package com.xuecheng.manage_cms_client.service.impl;

import com.mongodb.client.gridfs.GridFSBucket;
import com.mongodb.client.gridfs.GridFSDownloadStream;
import com.mongodb.client.gridfs.model.GridFSFile;
import com.xuecheng.framework.domain.cms.CmsPage;
import com.xuecheng.framework.domain.cms.CmsSite;
import com.xuecheng.manage_cms_client.dao.CmsPageRepository;
import com.xuecheng.manage_cms_client.dao.CmsSiteRepository;
import com.xuecheng.manage_cms_client.service.PageService;
import org.apache.commons.io.IOUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.data.mongodb.gridfs.GridFsResource;
import org.springframework.data.mongodb.gridfs.GridFsTemplate;
import org.springframework.stereotype.Service;

import java.io.*;
import java.util.Optional;

@Service
public class PageServiceImpl implements PageService {
    private static  final Logger LOGGER = LoggerFactory.getLogger(PageService.class);
    private GridFsTemplate gridFsTemplate;
    private GridFSBucket gridFSBucket;
    private CmsPageRepository cmsPageRepository;
    private CmsSiteRepository cmsSiteRepository;

    @Autowired
    public PageServiceImpl(GridFsTemplate gridFsTemplate, GridFSBucket gridFSBucket,
                           CmsPageRepository cmsPageRepository, CmsSiteRepository cmsSiteRepository){
        this.gridFsTemplate = gridFsTemplate;
        this.gridFSBucket = gridFSBucket;
        this.cmsPageRepository = cmsPageRepository;
        this.cmsSiteRepository = cmsSiteRepository;
    }

    @Override
    public CmsPage findCmsPageById(String pageId) {
        Optional<CmsPage> optional = cmsPageRepository.findById(pageId);
        if(optional.isPresent()){
            return optional.get();
        }
        return null;
    }

    @Override
    // 保存html页面到服务器物理路径
    public void savePageToServerPath(String pageId) {
        // 根据pageId查询cmsPage
        CmsPage cmsPage = this.findCmsPageById(pageId);
        if(cmsPage != null){
            // 得到html的文件id，从cmsPage中获取htmlFileId内容
            String htmlFileId = cmsPage.getHtmlFileId();
            // 从gridFS中查询html文件
            InputStream inputStream = this.getFileById(htmlFileId);
            if(inputStream == null){
                LOGGER.error("getFileById InputStream is null , htmlFileId:{}", htmlFileId);
                return;
            }
            // 得到站点id
            String siteId = cmsPage.getSiteId();
            // 得到站点的信息
            CmsSite cmsSite = this.findCmsSiteById(siteId);
            // 得到站点的物理路径
            String sitePhysicalPath = cmsSite.getSitePhysicalPath();
            // 得到页面的物理路径
            String pagePath = sitePhysicalPath + cmsPage.getPagePhysicalPath() + cmsPage.getPageName();
            // 将html文件保存到服务器物理路径上
            FileOutputStream fileOutputStream = null;
            try{
                fileOutputStream = new FileOutputStream(new File(pagePath));
                IOUtils.copy(inputStream, fileOutputStream);
            }catch (FileNotFoundException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }finally {
                try {
                    if(inputStream != null){
                        inputStream.close();
                    }
                    if(fileOutputStream != null){
                        fileOutputStream.close();
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    private CmsSite findCmsSiteById(String siteId) {
        Optional<CmsSite> optional = cmsSiteRepository.findById(siteId);
        if(optional.isPresent()){
            return optional.get();
        }
        return null;
    }

    // 根据文件id从GridFS中查询文件内容
    private InputStream getFileById(String fileId) {
        // 文件对象
        GridFSFile gridFSFile = gridFsTemplate.findOne(Query.query(Criteria.where("_id").is(fileId)));
        // 打开下载流
        GridFSDownloadStream gridFSDownloadStream = gridFSBucket.openDownloadStream(gridFSFile.getObjectId());
        // 定义GridFsResource
        GridFsResource gridFsResource = new GridFsResource(gridFSFile, gridFSDownloadStream);
        try {
            return gridFsResource.getInputStream();
        } catch (IOException e) {
            e.printStackTrace();
        }
        return null;
    }
}
